package net.ib.mtalk.provider;

import java.util.ArrayList;

import net.ib.mtalk.constant.HandlerMsgConst;
import net.ib.mtalk.database.DatabaseContract;
import net.ib.mtalk.database.DatabaseContract.BuddyTable;
import net.ib.mtalk.database.DatabaseContract.ContactTable;
import net.ib.mtalk.database.DatabaseContract.GroupTable;
import net.ib.mtalk.database.DatabaseContract.MessageTable;
import net.ib.mtalk.database.DatabaseContract.ParticipantsTable;
import net.ib.mtalk.database.DatabaseContract.ProfileTable;
import net.ib.mtalk.database.DatabaseContract.SuggestionTable;
import net.ib.mtalk.database.DatabaseContract.ViewMembersTable;
import net.ib.mtalk.database.DatabaseContract.ViewTable;
import net.ib.mtalk.database.DatabaseHelper;
import net.ib.mtalk.database.DatabaseHelper.Buddy_Query;
import net.ib.mtalk.database.DatabaseHelper.Contact_Query;
import net.ib.mtalk.database.DatabaseHelper.Tables;
import net.ib.mtalk.database.SQLBuilder;
import net.ib.mtalk.ui.buddy.info.GoContactAdapter;
import net.ib.mtalk.util.MTalkLogWriter;
import android.content.ContentProvider;
import android.content.ContentProviderOperation;
import android.content.ContentProviderResult;
import android.content.ContentValues;
import android.content.Context;
import android.content.OperationApplicationException;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.util.Log;

/**
 * ChatON ContentProvider
 *  
 * @author zoozung
 *
 */
public class MTalkProvider extends ContentProvider {
	
	public static final String AUTHORITY		=	"net.ib.mtalk.provider";
	
	private DatabaseHelper mDbHelper;
	
	private static final UriMatcher sUriMatcher = buildUriMatcher();
	
	private static final int BUDDY					= 100;
	private static final int BUDDY_ID				= 101;
	private static final int BUDDY_UUID_MSB			= 102;
	private static final int BUDDY_UUID_LSB			= 103;
	private static final int BUDDY_STATUS_TYPE		= 104;
	private static final int BUDDY_INFO				= 105;
	private static final int BUDDY_NEW_FRIEND		= 106;
	private static final int BUDDY_CHOSUNG			= 107;
	private static final int BUDDY_IMG_VERSION		= 108;
	private static final int BUDDY_NOT_GROUP		= 109;
	private static final int BUDDY_UNION			= 110;
	
	private static final int GROUP					= 200;
	private static final int GROUP_ID				= 201;
	private static final int GROUP_NAME				= 202;
	private static final int GROUP_SET_FOLD			= 203;
	private static final int GROUP_BUDDY_INFO		= 204;
//	private static final int GROUP_PARTICIPANT_MSB	= 203;
//	private static final int GROUP_PARTICIPANT_LSB	= 204;
	
	private static final int CONTACT				= 300;
	private static final int CONTACT_ID				= 301;
	private static final int CONTACT_PHONE_ID		= 302;
	private static final int CONTACT_NUMBER			= 303;
	private static final int CONTACT_IDENTIFIER		= 304;
	private static final int CONTACT_TYPE			= 305;
	private static final int CONTACT_VERSIOIN		= 306;
	private static final int CONTACT_NAME			= 307;
	private static final int CONTACT_BUDDY_UUID_MSB	= 308;
	private static final int CONTACT_BUDDY_UUID_LSB	= 309;
	private static final int CONTACT_BUDDY			= 310;
	
	private static final int PARTICIPANTS			= 400;
	private static final int PARTICIPANTS_ID		= 401;
	private static final int PARTICIPANTS_GROUP		= 402;
	private static final int PARTICIPANTS_BUDDY		= 403;
	private static final int BUDDY_GROUP			= 404;
	
	private static final int MESSAGE				= 500;
	private static final int MESSAGE_ID				= 501;
	private static final int MESSAGE_CLIENT_UUID_MSB= 502;
	private static final int MESSAGE_CLIENT_UUID_LSB= 503;
	private static final int MESSAGE_UUID_MSB		= 504;
	private static final int MESSAGE_UUID_LSB		= 505;

	private static final int VIEW					= 600;
	private static final int VIEW_ID				= 601;
	private static final int VIEW_CLIENT_UUID_MSB	= 602;
	private static final int VIEW_CLIENT_UUID_LSB	= 603;
	private static final int VIEW_UUID_MSB			= 604;
	private static final int VIEW_UUID_LSB			= 605;
	private static final int VIEW_RECEIVER_MSB		= 606;
	private static final int VIEW_RECEIVER_LSB		= 607;
	
	private static final int SUGGESTION				= 700;
	private static final int SUGGESTION_ID			= 701;
	private static final int SUGGESTION_UUID_MSB	= 702;
	private static final int SUGGESTION_UUID_LSB	= 703;
	private static final int SUGGESTION_STATUS_TYPE	= 704;
	private static final int SUGGESTION_DISPLAYNAME	= 705;
	
	private static final int VIEW_MEMBERS			= 800;
	private static final int VIEW_MEMBERS_ID		= 801;
	
	private static final int PROFILE				= 900;
	private static final int PROFILE_ID				= 901;
	private static final int PROFILE_UUID_MSB		= 902;
	private static final int PROFILE_UUID_LSB		= 903;
	
	/**
	 * Item 의 type 을 return 
	 */
	@Override
	public String getType(Uri uri) {
		final int match = sUriMatcher.match(uri);
		switch (match) {
		case BUDDY:
			return BuddyTable.CONTENT_TYPE;
		case BUDDY_ID:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_UUID_MSB:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_UUID_LSB:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_STATUS_TYPE:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_INFO:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_NEW_FRIEND:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_CHOSUNG:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_IMG_VERSION:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_NOT_GROUP:
			return BuddyTable.CONTENT_ITEM_TYPE;
		case BUDDY_UNION:
			return BuddyTable.CONTENT_ITEM_TYPE;
			
		case GROUP:
			return GroupTable.CONTENT_TYPE;
		case GROUP_ID:
			return GroupTable.CONTENT_ITEM_TYPE;
		case GROUP_NAME:
			return GroupTable.CONTENT_ITEM_TYPE;
		case GROUP_SET_FOLD:
			return GroupTable.CONTENT_ITEM_TYPE;
		case GROUP_BUDDY_INFO:
			return GroupTable.CONTENT_ITEM_TYPE;
//		case GROUP_PARTICIPANT_MSB:
//			return GroupTable.CONTENT_ITEM_TYPE;
//		case GROUP_PARTICIPANT_LSB:
//			return GroupTable.CONTENT_ITEM_TYPE;
			
		case CONTACT:
			return ContactTable.CONTENT_TYPE;
		case CONTACT_ID:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_PHONE_ID:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_NUMBER:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_IDENTIFIER:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_TYPE:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_VERSIOIN:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_NAME:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_BUDDY_UUID_MSB:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_BUDDY_UUID_LSB:
			return ContactTable.CONTENT_ITEM_TYPE;
		case CONTACT_BUDDY:
			return ContactTable.CONTENT_ITEM_TYPE;
			
		case PARTICIPANTS:
			return ParticipantsTable.CONTENT_TYPE;
		case PARTICIPANTS_ID:
			return ParticipantsTable.CONTENT_ITEM_TYPE;
		case PARTICIPANTS_GROUP:
			return ParticipantsTable.CONTENT_ITEM_TYPE;
		case PARTICIPANTS_BUDDY:
			return ParticipantsTable.CONTENT_ITEM_TYPE;
		case BUDDY_GROUP:
			return ParticipantsTable.CONTENT_ITEM_TYPE;
		
		case MESSAGE:
			return MessageTable.CONTENT_TYPE;
		case MESSAGE_ID:
			return MessageTable.CONTENT_ITEM_TYPE;
		case MESSAGE_CLIENT_UUID_MSB:
			return MessageTable.CONTENT_ITEM_TYPE;
		case MESSAGE_CLIENT_UUID_LSB:
			return MessageTable.CONTENT_ITEM_TYPE;
		case MESSAGE_UUID_MSB:
			return MessageTable.CONTENT_ITEM_TYPE;
		case MESSAGE_UUID_LSB:
			return MessageTable.CONTENT_ITEM_TYPE;
			
		case VIEW:
			return ViewTable.CONTENT_TYPE;
		case VIEW_ID:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_CLIENT_UUID_MSB:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_CLIENT_UUID_LSB:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_UUID_MSB:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_UUID_LSB:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_RECEIVER_MSB:
			return ViewTable.CONTENT_ITEM_TYPE;
		case VIEW_RECEIVER_LSB:
			return ViewTable.CONTENT_ITEM_TYPE;
			
		case SUGGESTION:
			return SuggestionTable.CONTENT_TYPE;
		case SUGGESTION_ID:
			return SuggestionTable.CONTENT_ITEM_TYPE;
		case SUGGESTION_UUID_MSB:
			return SuggestionTable.CONTENT_ITEM_TYPE;
		case SUGGESTION_UUID_LSB:
			return SuggestionTable.CONTENT_ITEM_TYPE;
		case SUGGESTION_STATUS_TYPE:
			return SuggestionTable.CONTENT_ITEM_TYPE;
		case SUGGESTION_DISPLAYNAME:
			return SuggestionTable.CONTENT_ITEM_TYPE;
		
		case VIEW_MEMBERS:
			return ViewMembersTable.CONTENT_TYPE;
		case VIEW_MEMBERS_ID:
			return ViewMembersTable.CONTENT_ITEM_TYPE;

		case PROFILE:
			return ProfileTable.CONTENT_TYPE;
		case PROFILE_ID:
			return ProfileTable.CONTENT_ITEM_TYPE;
		case PROFILE_UUID_MSB:
			return ProfileTable.CONTENT_ITEM_TYPE;
		case PROFILE_UUID_LSB:
			return ProfileTable.CONTENT_ITEM_TYPE;
		
		default:
			throw new UnsupportedOperationException("UnKonwn Uri : " + uri);
		}
	}

	@Override
	public Cursor query(Uri uri, String[] projection, String selection,
			String[] selectionArgs, String sortOrder) {
		final SQLiteDatabase db = mDbHelper.getReadableDatabase();
		
		final int match = sUriMatcher.match(uri);
		Cursor cCursor = null;
		
		final SQLBuilder builder = setSQLBuild(uri, match).where(selection, selectionArgs);;
		cCursor = builder.query(db, projection, sortOrder);
				
		if (cCursor != null)
			cCursor.setNotificationUri(getContext().getContentResolver(), uri);
		
		return cCursor;
	}
	
	/**
	 * Uri 에 맞춰서 Query 를 만든다.
	 * 
	 * @param uri
	 * @param match
	 * @return
	 */
	private SQLBuilder setSQLBuild(Uri uri, int match) {
		final SQLBuilder builder = new SQLBuilder();
		switch (match) {
		case BUDDY: {
			return builder.table(Tables.TABLE_NAME_BUDDY);
		}
		case BUDDY_ID: {
			final String buddyID = BuddyTable.getBuddyID(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
					.where(BuddyTable._ID + "=?", buddyID);
		}
		case BUDDY_UUID_MSB: {
			final String buddyUUIDMSB = BuddyTable.getBuddyUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
					.where(BuddyTable.KEY_BUDDY_UUID_MSB + "=?", buddyUUIDMSB);
		}
		case BUDDY_UUID_LSB: {
			final String buddyUUIDLSB = BuddyTable.getBuddyUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
					.where(BuddyTable.KEY_BUDDY_UUID_LSB + "=?", buddyUUIDLSB);
		}
		case BUDDY_STATUS_TYPE: {
			final String statusType = BuddyTable.getBuddyStatusType(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
			.where(BuddyTable.KEY_BUDDY_STATUS_TYPE + "=?", statusType);
		}
		case BUDDY_INFO: {
			final String buddyInfo = BuddyTable.getBuddyInfo(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
					.where(BuddyTable.KEY_BUDDY_INFO + "=?", buddyInfo);
		}
		case BUDDY_NEW_FRIEND: {
			final String newfriend = BuddyTable.getNewFriend(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
			.where(BuddyTable.KEY_BUDDY_NEW_FRIEND+ "=?", newfriend);
		}
		case BUDDY_CHOSUNG: {
			final String chosung = BuddyTable.getChosung(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
			.where(BuddyTable.KEY_BUDDY_CHOSUNG+ "=?", chosung);
		}
		case BUDDY_IMG_VERSION: {
			final String img_version = BuddyTable.getImgVersion(uri);
			return builder.table(Tables.TABLE_NAME_BUDDY)
			.where(BuddyTable.KEY_BUDDY_IMG_VERSION+ "=?", img_version);
		}
		case BUDDY_NOT_GROUP: { 
			return builder.table(Buddy_Query.BUDDY_NOT_GROUP);
		}
		case BUDDY_UNION: { 
			return builder.table(Buddy_Query.BUDDY_UNION);
		}
		
		case GROUP: {
			return builder.table(Tables.TABLE_NAME_GROUP);
		}
		case GROUP_ID : {
			final String groupID = GroupTable.getGroupID(uri);
			return builder.table(Tables.TABLE_NAME_GROUP)
					.where(GroupTable._ID + "=?", groupID);
		}
		case GROUP_NAME : {
			final String groupName = GroupTable.getGroupName(uri);
			return builder.table(Tables.TABLE_NAME_GROUP)
			.where(GroupTable.KEY_GROUP_NAME+ "=?", groupName);
		}
		case GROUP_SET_FOLD : {
			final String groupSetFold = GroupTable.getGroupSetFold(uri);
			return builder.table(Tables.TABLE_NAME_GROUP)
			.where(GroupTable.KEY_GROUP_SET_FOLD + "=?", groupSetFold);
		}
		case GROUP_BUDDY_INFO : {
			return builder.table(Buddy_Query.BUDDY_INFO);
		}
//		case GROUP_PARTICIPANT_MSB : {
//			final String groupMsb = GroupTable.getParticipantMsb(uri);
//			return builder.table(Tables.TABLE_NAME_GROUP)
//			.where(GroupTable.KEY_PARTICIPANT_MSB + "=?", groupMsb);
//		}
//		case GROUP_PARTICIPANT_LSB : {
//			final String groupLsb = GroupTable.getParticipantLsb(uri);
//			return builder.table(Tables.TABLE_NAME_GROUP)
//			.where(GroupTable.KEY_PARTICIPANT_LSB + "=?", groupLsb);
//		}
		
		case CONTACT: {
			return builder.table(Tables.TABLE_NAME_CONTACT);
		}
		case CONTACT_ID: {
			final String contactID = ContactTable.getContactID(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable._ID + "=?", contactID);
		}
		case CONTACT_PHONE_ID: {
			final String contactPhoneId = ContactTable.getContactPhoneId(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_CONTACT_PHONE_ID + "=?", contactPhoneId);
		}
		case CONTACT_NUMBER: {
			final String contactNumber = ContactTable.getContactNumber(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_CONTACT_NUMBER + "=?", contactNumber);
		}
		case CONTACT_IDENTIFIER: {
			final String contactIdentifier = ContactTable.getContactIdentifier(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_CONTACT_IDENTIFIER + "=?", contactIdentifier);
		}
		case CONTACT_TYPE: {
			final String contactType = ContactTable.getContactType(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_CONTACT_TYPE + "=?", contactType);
		}
		case CONTACT_VERSIOIN: {
			final String contactVersion = ContactTable.getContactVersion(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_CONTACT_VERSION + "=?", contactVersion);
		}
		case CONTACT_NAME: {
			final String contactName = ContactTable.getContactName(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
			.where(ContactTable.KEY_CONTACT_NAME + "=?", contactName);
		}
		case CONTACT_BUDDY_UUID_MSB: {
			final String buddyUUIDMsb = ContactTable.getBuddyUUIDMsb(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_BUDDY_UUID_MSB + "=?", buddyUUIDMsb);
		}
		case CONTACT_BUDDY_UUID_LSB: {
			final String buddyUUIDLsb = ContactTable.getBuddyUUIDLsb(uri);
			return builder.table(Tables.TABLE_NAME_CONTACT)
					.where(ContactTable.KEY_BUDDY_UUID_LSB + "=?", buddyUUIDLsb);
		}
		case CONTACT_BUDDY: {
			return builder.table(Contact_Query.CONTACT_BUDDY);
		}
		
		case PARTICIPANTS: {
			return builder.table(Tables.TABLE_NAME_PARTICIPANTS);
		}
		case PARTICIPANTS_ID: { 
			final String participantsId = ParticipantsTable.getParticipantsID(uri);
			return builder.table(Tables.TABLE_NAME_PARTICIPANTS)
					.where(ParticipantsTable._ID + "=?", participantsId);
		}
		case PARTICIPANTS_GROUP: { 
			final String participantsGroup = ParticipantsTable.getParticipantsGroupId(uri);
			return builder.table(Tables.TABLE_NAME_PARTICIPANTS)
			.where(ParticipantsTable.KEY_PARTICIPANTS_GROUP + "=?", participantsGroup);
		}
		case PARTICIPANTS_BUDDY: { 
			final String participantsBuddy = ParticipantsTable.getParticipantsBuddyId(uri);
			return builder.table(Tables.TABLE_NAME_PARTICIPANTS)
			.where(ParticipantsTable.KEY_PARTICIPANTS_BUDDY + "=?", participantsBuddy);
		}
		case BUDDY_GROUP: { 
			return builder.table(Buddy_Query.BUDDY_GROUP);
		}
		
		case MESSAGE: {
			return builder.table(Tables.TABLE_NAME_MESSAGE);
		}
		case MESSAGE_ID: {
			final String messageID = MessageTable.getMessageID(uri);
			return builder.table(Tables.TABLE_NAME_MESSAGE)
					.where(MessageTable._ID+"=?", messageID);
		}
		case MESSAGE_CLIENT_UUID_MSB: {
			final String messageClientUUIDMSB = MessageTable.getMessageClientUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_MESSAGE)
					.where(MessageTable.KEY_CLIENT_VIEW_UUID_MSB + "=?", messageClientUUIDMSB);
		}
		case MESSAGE_CLIENT_UUID_LSB: {
			final String messageClientUUIDLSB = MessageTable.getMessageClientUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_MESSAGE)
			.where(MessageTable.KEY_CLIENT_VIEW_UUID_LSB + "=?", messageClientUUIDLSB);
		}
		case MESSAGE_UUID_MSB: {
			final String messageUUIDMSB = MessageTable.getMessageUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_MESSAGE)
					.where(MessageTable.KEY_MESSAGE_UUID_MSB + "=?", messageUUIDMSB);
		}
		case MESSAGE_UUID_LSB: {
			final String messageUUIDLSB = MessageTable.getMessageUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_MESSAGE)
					.where(MessageTable.KEY_MESSAGE_UUID_MSB + "=?", messageUUIDLSB);
		}
		
		case VIEW: {
			return builder.table(Tables.TABLE_NAME_VIEW);
		}
		case VIEW_ID: {
			final String viewID = ViewTable.getViewID(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable._ID+"=?", viewID);
		}
		case VIEW_CLIENT_UUID_MSB: {
			final String viewClientUUIDMSB = ViewTable.getViewClientUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_CLIENT_VIEW_UUID_MSB, viewClientUUIDMSB);
		}
		case VIEW_CLIENT_UUID_LSB: {
			final String viewClientUUIDLSB = ViewTable.getViewClientUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_CLIENT_VIEW_UUID_LSB, viewClientUUIDLSB);
		}
		case VIEW_UUID_MSB: {
			final String viewUUIDMSB = ViewTable.getViewUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_VIEW_UUID_MSB + "=?", viewUUIDMSB);
		}
		case VIEW_UUID_LSB: {
			final String viewUUIDLSB = ViewTable.getViewUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_VIEW_UUID_LSB + "=?", viewUUIDLSB);
		}
		case VIEW_RECEIVER_MSB: {
			final String viewReceiverMsb = ViewTable.getReceiverMsb(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_RECEIVER_UUID_MSB + "=?", viewReceiverMsb);
		}
		case VIEW_RECEIVER_LSB: {
			final String viewReceiverLsb = ViewTable.getReceiverLsb(uri);
			return builder.table(Tables.TABLE_NAME_VIEW)
			.where(ViewTable.KEY_RECEIVER_UUID_LSB + "=?", viewReceiverLsb);
		}
		
		case SUGGESTION: {
			return builder.table(Tables.TABLE_NAME_SUGGESTION);
		}
		case SUGGESTION_ID: {
			final String suggestionID = SuggestionTable.getSuggestionID(uri);
			return builder.table(Tables.TABLE_NAME_SUGGESTION)
			.where(SuggestionTable._ID+"=?", suggestionID);
		}
		case SUGGESTION_UUID_MSB: {
			final String suggestionUUIDMSB = SuggestionTable.getSuggestionUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_SUGGESTION)
			.where(SuggestionTable.KEY_SUGGESTION_UUID_MSB + "=?", suggestionUUIDMSB);
		}
		case SUGGESTION_UUID_LSB: {
			final String suggestionUUIDLSB = SuggestionTable.getSuggestionUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_SUGGESTION)
			.where(SuggestionTable.KEY_SUGGESTION_UUID_LSB + "=?", suggestionUUIDLSB);
		}
		case SUGGESTION_STATUS_TYPE: {
			final String suggestionStatusType = SuggestionTable.getSuggestionStatusType(uri);
			return builder.table(Tables.TABLE_NAME_SUGGESTION)
			.where(SuggestionTable.KEY_STATUS_TYPE+ "=?", suggestionStatusType);
		}
		case SUGGESTION_DISPLAYNAME: {
			final String suggestionDisplayName = SuggestionTable.getSuggestionDisplayName(uri);
			return builder.table(Tables.TABLE_NAME_SUGGESTION)
			.where(SuggestionTable.KEY_DISPLAYNAME+ "=?", suggestionDisplayName);
		}

		case VIEW_MEMBERS: {
			return builder.table(Tables.TABLE_NAME_VIEW_MEMBERS);
		}
		case VIEW_MEMBERS_ID: {
			final String viewMembersID = ViewMembersTable.getViewMembersID(uri);//ViewTable.getViewID(uri);
			return builder.table(Tables.TABLE_NAME_VIEW_MEMBERS)
			.where(ViewMembersTable._ID+"=?", viewMembersID);
		}
		
		case PROFILE: {
			return builder.table(Tables.TABLE_NAME_PROFILE);
		}
		case PROFILE_ID: {
			final String profileID = ProfileTable.getProfileID(uri);
			return builder.table(Tables.TABLE_NAME_PROFILE)
			.where(ProfileTable._ID+"=?", profileID);
		}
		case PROFILE_UUID_MSB: {
			final String profileUUIDMSB = ProfileTable.getProfileUUIDMSB(uri);
			return builder.table(Tables.TABLE_NAME_PROFILE)
			.where(ProfileTable.KEY_PROFILE_UUID_MSB+"=?", profileUUIDMSB);
		}
		case PROFILE_UUID_LSB: {
			final String profileUUIDLSB = ProfileTable.getProfileUUIDLSB(uri);
			return builder.table(Tables.TABLE_NAME_PROFILE)
			.where(ProfileTable.KEY_PROFILE_UUID_LSB+"=?", profileUUIDLSB);
		}
		
		default:
			return null;
		}
	}
	
	@Override
	public boolean onCreate() {		
		Log.v("SQLITEDATABASE", "MTalkProvider.onCreate()");
		final Context context = getContext();
		mDbHelper = new DatabaseHelper(context);
		return true;
	}

	@Override
	public Uri insert(Uri uri, ContentValues values) {
		final SQLiteDatabase db = mDbHelper.getWritableDatabase();
		final int matcher = sUriMatcher.match(uri);
		Uri returnUri = null;
		
		try{
			switch (matcher) {
				case BUDDY: {
					final long buddyId = db.insertOrThrow(Tables.TABLE_NAME_BUDDY, null, values);
					returnUri = BuddyTable.CONTENT_URI;
				}
				break;
				case GROUP: {
					final long groupId = db.insertOrThrow(Tables.TABLE_NAME_GROUP, null, values);
					returnUri = GroupTable.buildGroupUri(String.valueOf(groupId));
				}
				break;
				case CONTACT: {
					final long contactId = db.insertOrThrow(Tables.TABLE_NAME_CONTACT, null, values);
					returnUri = ContactTable.buildContactUri(String.valueOf(contactId));
					break;
				}
				case PARTICIPANTS: {
					final long participantsId = db.insertOrThrow(Tables.TABLE_NAME_PARTICIPANTS, null, values);
					returnUri = ContactTable.buildContactUri(String.valueOf(participantsId));
					break;
				}
				case MESSAGE: {
					final long messageId = db.insertOrThrow(Tables.TABLE_NAME_MESSAGE, null, values);
					returnUri = MessageTable.buildMessageUri(String.valueOf(messageId));
					break;
				}
				case VIEW: {
					final long viewId = db.insertOrThrow(Tables.TABLE_NAME_VIEW, null, values);
					returnUri = ViewTable.buildViewUri(String.valueOf(viewId));
					break;
				}
				case SUGGESTION: {
					final long suggestionId = db.insertOrThrow(Tables.TABLE_NAME_SUGGESTION, null, values);
					returnUri = SuggestionTable.buildSuggestionUri(String.valueOf(suggestionId));
					break;
				}
				case VIEW_MEMBERS : {
					final long viewMembersId = db.insertOrThrow(Tables.TABLE_NAME_VIEW_MEMBERS, null, values);
					returnUri = ViewMembersTable.buildViewMembersUri(String.valueOf(viewMembersId));
					break;
				}
				case PROFILE: {
					final long profileId = db.insertOrThrow(Tables.TABLE_NAME_PROFILE, null, values);
					returnUri = ProfileTable.buildProfileUri(String.valueOf(profileId));
					break;
				}
				default: {
	
				}
			}
			getContext().getContentResolver().notifyChange(returnUri, null);
		} catch(Exception e){
			MTalkLogWriter.e(e);
		}
		return returnUri;
	}

	@Override
	public int update(Uri uri, ContentValues values, String selection,
			String[] selectionArgs) {
		final SQLiteDatabase db = mDbHelper.getWritableDatabase();
		final int matcher = sUriMatcher.match(uri);
		int returnInteger = -1;
		SQLBuilder builder = setSQLBuild(uri, matcher);
		
		returnInteger = builder.where(selection, selectionArgs).update(db, values);
		if (returnInteger > 0) {
			getContext().getContentResolver().notifyChange(uri, null);
		}
		return returnInteger;
	}

	@Override
	public int delete(Uri uri, String selection, String[] selectionArgs) {
		final SQLiteDatabase db = mDbHelper.getWritableDatabase();
		final int matcher = sUriMatcher.match(uri);
		int returnInteger = -1;
		final SQLBuilder builder = setSQLBuild(uri, matcher).where(selection, selectionArgs);

		returnInteger = builder.delete(db);
		if (returnInteger > 0){
			getContext().getContentResolver().notifyChange(DatabaseContract.AUTHORITY_URI, null);
		}
		return returnInteger;
	}

	private static UriMatcher buildUriMatcher() {
		final UriMatcher matcher = new UriMatcher(UriMatcher.NO_MATCH);
		final String authority = DatabaseContract.CONTENT_AUTHORITY;
		
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY, BUDDY);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/#", BUDDY_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_UUID_MSB + "/#", BUDDY_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_UUID_LSB + "/#", BUDDY_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_STATUS_TYPE + "/#", BUDDY_STATUS_TYPE);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_INFO + "/#", BUDDY_INFO);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_NEW_FRIEND + "/#", BUDDY_NEW_FRIEND);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_CHOSUNG + "/#", BUDDY_CHOSUNG);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.KEY_BUDDY_IMG_VERSION + "/#", BUDDY_IMG_VERSION);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.PATH_NOT_GROUP, BUDDY_NOT_GROUP);
		matcher.addURI(authority, Tables.TABLE_NAME_BUDDY + "/" + BuddyTable.PATH_UNION, BUDDY_UNION);
				
		matcher.addURI(authority, Tables.TABLE_NAME_GROUP, GROUP);
		matcher.addURI(authority, Tables.TABLE_NAME_GROUP + "/#", GROUP_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_GROUP + "/" + GroupTable.KEY_GROUP_NAME + "/#", GROUP_NAME);
		matcher.addURI(authority, Tables.TABLE_NAME_GROUP + "/" + GroupTable.KEY_GROUP_SET_FOLD + "/#", GROUP_SET_FOLD);
		matcher.addURI(authority, Tables.TABLE_NAME_GROUP + "/" + GroupTable.PATH_BUDDY_INFO, GROUP_BUDDY_INFO);
		
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT, CONTACT);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/#", CONTACT_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_PHONE_ID + "/#", CONTACT_PHONE_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_NUMBER + "/#", CONTACT_NUMBER);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_IDENTIFIER + "/#", CONTACT_IDENTIFIER);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_TYPE +"/#", CONTACT_TYPE);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_VERSION +"/#", CONTACT_VERSIOIN);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_CONTACT_NAME +"/#", CONTACT_NAME);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_BUDDY_UUID_MSB +"/#", CONTACT_BUDDY_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.KEY_BUDDY_UUID_LSB +"/#", CONTACT_BUDDY_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_CONTACT + "/" + ContactTable.PATH_CONTACT_BUDDY, CONTACT_BUDDY);
		
		matcher.addURI(authority, Tables.TABLE_NAME_PARTICIPANTS, PARTICIPANTS);
		matcher.addURI(authority, Tables.TABLE_NAME_PARTICIPANTS + "/#", PARTICIPANTS_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_PARTICIPANTS + "/" + ParticipantsTable.KEY_PARTICIPANTS_GROUP+ "/#", PARTICIPANTS_GROUP);
		matcher.addURI(authority, Tables.TABLE_NAME_PARTICIPANTS + "/" + ParticipantsTable.KEY_PARTICIPANTS_BUDDY+ "/#", PARTICIPANTS_BUDDY);
		matcher.addURI(authority, Tables.TABLE_NAME_PARTICIPANTS + "/" + ParticipantsTable.PATH_GROUP, BUDDY_GROUP);
		
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE, MESSAGE);
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE + "/#", MESSAGE_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE + "/" + MessageTable.KEY_CLIENT_VIEW_UUID_MSB + "/#", MESSAGE_CLIENT_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE + "/" + MessageTable.KEY_CLIENT_VIEW_UUID_LSB + "/#", MESSAGE_CLIENT_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE + "/" + MessageTable.KEY_MESSAGE_UUID_MSB + "/#", MESSAGE_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_MESSAGE + "/" + MessageTable.KEY_MESSAGE_UUID_LSB + "/#", MESSAGE_UUID_LSB);

		matcher.addURI(authority, Tables.TABLE_NAME_VIEW, VIEW);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/#", VIEW_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_CLIENT_VIEW_UUID_MSB + "/#", VIEW_CLIENT_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_CLIENT_VIEW_UUID_LSB + "/#", VIEW_CLIENT_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_VIEW_UUID_MSB + "/#", VIEW_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_VIEW_UUID_LSB + "/#", VIEW_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_RECEIVER_UUID_MSB + "/#", VIEW_RECEIVER_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW + "/" + ViewTable.KEY_RECEIVER_UUID_LSB + "/#", VIEW_RECEIVER_LSB);
		
		matcher.addURI(authority, Tables.TABLE_NAME_SUGGESTION, SUGGESTION);
		matcher.addURI(authority, Tables.TABLE_NAME_SUGGESTION + "/#", SUGGESTION_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_SUGGESTION + "/" + SuggestionTable.KEY_SUGGESTION_UUID_MSB + "/#", SUGGESTION_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_SUGGESTION + "/" + SuggestionTable.KEY_SUGGESTION_UUID_LSB + "/#", SUGGESTION_UUID_LSB);
		matcher.addURI(authority, Tables.TABLE_NAME_SUGGESTION + "/" + SuggestionTable.KEY_STATUS_TYPE + "/#", SUGGESTION_STATUS_TYPE);
		
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW_MEMBERS, VIEW_MEMBERS);
		matcher.addURI(authority, Tables.TABLE_NAME_VIEW_MEMBERS + "/#", VIEW_MEMBERS_ID);
		
		matcher.addURI(authority, Tables.TABLE_NAME_PROFILE, PROFILE);
		matcher.addURI(authority, Tables.TABLE_NAME_PROFILE + "/#", PROFILE_ID);
		matcher.addURI(authority, Tables.TABLE_NAME_PROFILE + "/" + ProfileTable.KEY_PROFILE_UUID_MSB + "/#", PROFILE_UUID_MSB);
		matcher.addURI(authority, Tables.TABLE_NAME_PROFILE + "/" + ProfileTable.KEY_PROFILE_UUID_LSB + "/#", PROFILE_UUID_LSB);

		return matcher;
	}
	
	@Override
	public ContentProviderResult[] applyBatch(
			ArrayList<ContentProviderOperation> operations)
			throws OperationApplicationException {
		final SQLiteDatabase db = mDbHelper.getWritableDatabase();
		db.beginTransaction();
		try {
			final int numOperation = operations.size();
			final ContentProviderResult[] result = new ContentProviderResult[numOperation];
			for (int i=0; i<numOperation; i++) {
				result[i] = operations.get(i).apply(this, result, i);
			}
			db.setTransactionSuccessful();
			return result;
			
		} finally {
			db.endTransaction();
		}
	}
}
